package com.example.spb6;

import static androidx.constraintlayout.helper.widget.MotionEffect.TAG;
import static com.example.spb6.MedicineActivity.DB_PASSWORD;
import static com.example.spb6.MedicineActivity.DB_URL;
import static com.example.spb6.MedicineActivity.DB_USER;

import androidx.appcompat.app.AppCompatActivity;
import androidx.core.app.ActivityCompat;
import androidx.core.app.NotificationCompat;

import android.Manifest;
import android.app.AlertDialog;
import android.app.Notification;
import android.app.NotificationChannel;
import android.app.NotificationManager;
import android.app.PendingIntent;
import android.bluetooth.BluetoothAdapter;
import android.bluetooth.BluetoothDevice;
import android.bluetooth.BluetoothSocket;
import android.content.Context;
import android.content.Intent;
import android.media.AudioAttributes;
import android.media.MediaPlayer;
import android.media.RingtoneManager;
import android.net.Uri;
import android.os.AsyncTask;
import android.os.Build;
import android.os.Bundle;
import android.os.CountDownTimer;
import android.os.Handler;
import android.os.Looper;
import android.os.Vibrator;
import android.util.Log;
import android.view.View;
import android.widget.Button;
import android.widget.TextView;
import android.widget.Toast;

import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.Statement;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Calendar;
import java.util.Date;
import java.util.List;
import java.util.Locale;
import java.util.UUID;

public class Medicine_MainActivity extends AppCompatActivity {

    private TextView currentTimeTextView;
    private TextView temperatureHumidityTextView;
    private TextView nextMedicineTimeTextView;
    private TextView medicineNameTextView;
    private TextView medicineDosageTextView;
    private TextView medicineInfoTextView;
    private Handler handler;
    private Runnable updateTimeRunnable;
    private String mAddress;
    private BluetoothAdapter mBlueToothAdapter;
    private BluetoothDevice mDevice;
    private BluetoothSocket mBluetoothSocket;
    private final UUID mUUID = UUID.fromString( "00001101-0000-1000-8000-00805F9B34FB" );//蓝牙串口服务的UUID
    private String mSendContentStr;
    private static OutputStream mOS;

    private String mName;
    public ArrayList<String> requestList = new ArrayList<>();

    // 新增用于每秒发送当前时间的Handler和Runnable
    private Handler sendTimeHandler;
    private Runnable sendCurrentTimeRunnable;

    // 新增用于检查吃药时间的Handler和Runnable
    private Handler checkMedicineTimeHandler;
    private Runnable checkMedicineTimeRunnable;

    private Handler syncHandler;
    private Runnable syncRunnable;
    private Handler checkStockAndExpiryHandler;
    private Runnable checkStockAndExpiryRunnable;

    // 添加一个全局变量来跟踪当前的MediaPlayer
    private MediaPlayer currentMediaPlayer;
    // 添加一个标志位来记录是否正在播放提醒音
    private boolean isPlayingAlarmSound = false;
    // 添加一个变量用于停止铃声的Handler
    private Handler alarmStopHandler = new Handler();
    private CountDownTimer alarmTimer;
    private List<Medicine> medicineList;
    private boolean isDialogShowing = false;
    private String lastReminderTime = ""; // 记录上次提醒的时间
    private static final int MAX_MEDS_TO_SEND = 4; // 定义最大发送数量
    private Boolean isBluetoothConnected = false;
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        Intent intent = getIntent();
        super.onCreate( savedInstanceState );
        setContentView( R.layout.activity_main );
        medicineList = new ArrayList<>();
        Bundle bundle = intent.getExtras();
        if (bundle != null) {
            mAddress = bundle.getString( "address" );
            mName = bundle.getString( "name" );
            // 使用address和name做进一步处理
        }

        currentTimeTextView = findViewById( R.id.current_time_text_view );
        temperatureHumidityTextView = findViewById( R.id.temperature_humidity_text_view );
        nextMedicineTimeTextView = findViewById( R.id.next_medicine_time_text_view );
        medicineNameTextView = findViewById( R.id.medicine_name_text_view );
        medicineDosageTextView = findViewById( R.id.medicine_dosage_text_view );
        medicineInfoTextView = findViewById( R.id.medicine_info_text_view );
        handler = new Handler();
        updateTimeRunnable = new Runnable() {
            @Override
            public void run() {
                updateCurrentTime();
                handler.postDelayed( this, 1000 );
            }
        };

        // 初始化发送时间的Handler和Runnable
        sendTimeHandler = new Handler( Looper.getMainLooper() );
        sendCurrentTimeRunnable = new Runnable() {
            @Override
            public void run() {
                sendCurrentTime();
                sendTimeHandler.postDelayed( this, 1000 );
            }
        };

        // 初始化检查吃药时间的Handler和Runnable
        checkMedicineTimeHandler = new Handler( Looper.getMainLooper() );
        checkMedicineTimeRunnable = new Runnable() {
            @Override
            public void run() {
                checkMedicineTime();
                checkMedicineTimeHandler.postDelayed( this, 1000 );
            }
        };
        // 初始化检查库存和过期时间的Handler和Runnable
        checkStockAndExpiryHandler = new Handler( Looper.getMainLooper() );
        checkStockAndExpiryRunnable = new Runnable() {
            @Override
            public void run() {
                checkMedicineStockAndExpiry();
                checkStockAndExpiryHandler.postDelayed( this, 3000 );
            }
        };
        // 找到新增的按钮并设置点击事件监听器
        Button sendMedicineInfoButton = findViewById( R.id.send_medicine_info );
        sendMedicineInfoButton.setOnClickListener( new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                sendMedicineInfo();
            }
        } );

        connectDevice();
    }

    public void openMedicineWarehouse(View view) {
        Intent intent = new Intent( this, MedicineActivity.class );
        startActivityForResult( intent, 1 );
    }

    @Override
    protected void onResume() {
        super.onResume();
        loadMedicinesFromDatabase(); // 从数据库中重新加载药品信息
        handler.post( updateTimeRunnable );
        // 启动每秒发送当前时间的任务
        sendTimeHandler.post( sendCurrentTimeRunnable );
        // 启动每秒检查吃药时间的任务
        checkMedicineTimeHandler.post( checkMedicineTimeRunnable );
        // 启动检查库存和过期时间的任务
        checkStockAndExpiryHandler.post( checkStockAndExpiryRunnable );
        // 启动定时同步任务
        syncHandler = new Handler();
        syncRunnable = new Runnable() {
            @Override
            public void run() {
                sendMedicineInfo();
                syncHandler.postDelayed( this, 6000 ); // 每分钟同步一次
            }
        };
        syncHandler.post( syncRunnable );
    }

    @Override
    protected void onPause() {
        super.onPause();
        handler.removeCallbacks( updateTimeRunnable );
        // 停止每秒发送当前时间的任务
        sendTimeHandler.removeCallbacks( sendCurrentTimeRunnable );
        // 停止每秒检查吃药时间的任务
        checkMedicineTimeHandler.removeCallbacks( checkMedicineTimeRunnable );
        // 停止检查库存和过期时间的任务
        checkStockAndExpiryHandler.removeCallbacks( checkStockAndExpiryRunnable );
        syncHandler.removeCallbacks( syncRunnable );
    }

    private void updateCurrentTime() {
        SimpleDateFormat sdf = new SimpleDateFormat( "HH:mm:ss", Locale.getDefault() );
        String currentTime = sdf.format( new Date() );
        currentTimeTextView.setText( "当前时间: " + currentTime );
    }

    @Override
    protected void onActivityResult(int requestCode, int resultCode, Intent data) {
        super.onActivityResult( requestCode, resultCode, data );
        if (requestCode == 1 && resultCode == RESULT_OK) {
            if (data != null) {
                // 获取药物信息
                String medicineInfo = data.getStringExtra( "medicine_info" );
                if (medicineInfo != null) {
                    medicineInfoTextView.setText( "已添加的药物信息: " + medicineInfo );
                    Log.d( "Medicine_MainActivity", "收到药物信息: " + medicineInfo );
                }

                // 重新加载药物数据并更新显示
                loadMedicinesFromDatabase();
                updateNextMedicineTime();

                // 找出最近需要服用的药物
                String[] nearestMedicineDetails = findNearestMedicine( medicineInfo );
                if (nearestMedicineDetails != null) {
                    nextMedicineTimeTextView.setText( "下次吃药时间: " + nearestMedicineDetails[1] );
                    medicineNameTextView.setText( "药名: " + nearestMedicineDetails[0] );
                    medicineDosageTextView.setText( "药量: " + nearestMedicineDetails[2] );
                } else {
                    nextMedicineTimeTextView.setText( "下次吃药时间: 无" );
                    medicineNameTextView.setText( "药名: 无" );
                    medicineDosageTextView.setText( "药量: 无" );
                }

                // 将更新后的药物信息发送到硬件设备
                sendMedicineInfo();
                sendMedicineInfof(medicineInfo);          // 同步硬件
                // 记录日志
                Log.d( "Medicine_MainActivity", "从药物管理页面接收到最新数据: " + medicineInfo );
            }
        }
    }


    private String[] findNearestMedicine(String medicineInfo) {
        if (medicineInfo == null || medicineInfo.isEmpty()) {
            return null;
        }

        String[] medicines = medicineInfo.split( "; " );
        String nearestMedicineName = null;
        String nearestMedicineTime = null;
        String nearestMedicineDosage = null;
        long nearestTimeMillis = Long.MAX_VALUE;

        // 获取当前时间
        Calendar now = Calendar.getInstance();
        int currentHour = now.get( Calendar.HOUR_OF_DAY );
        int currentMinute = now.get( Calendar.MINUTE );
        int currentTimeMinutes = currentHour * 60 + currentMinute;

        for (String medicine : medicines) {
            if (medicine.isEmpty()) continue;

            try {
                // 解析药物信息
                String name = extractValue( medicine, "药名: ", "," );
                String timeStr = extractValue( medicine, "吃药时间: ", "," );
                String dosage = extractValue( medicine, "用量: ", ";" );

                if (name == null || timeStr == null || dosage == null) {
                    continue;
                }

                // 处理多个时间
                String[] times = timeStr.split( ", " );
                for (String time : times) {
                    String[] timeParts = time.trim().split( ":" );
                    if (timeParts.length != 2) continue;

                    int hour = Integer.parseInt( timeParts[0] );
                    int minute = Integer.parseInt( timeParts[1] );
                    int medicineTimeMinutes = hour * 60 + minute;

                    // 计算与当前时间的差值（考虑跨天情况）
                    int diffMinutes;
                    if (medicineTimeMinutes <= currentTimeMinutes) {
                        // 如果药物时间已经过去，计算到明天这个时间的分钟数
                        diffMinutes = (24 * 60 - currentTimeMinutes) + medicineTimeMinutes;
                    } else {
                        // 如果药物时间还未到，直接计算差值
                        diffMinutes = medicineTimeMinutes - currentTimeMinutes;
                    }
                    // 更新最近的药物
                    if (diffMinutes < nearestTimeMillis) {
                        nearestTimeMillis = diffMinutes;
                        nearestMedicineName = name;
                        nearestMedicineTime = time;
                        nearestMedicineDosage = dosage;
                    }
                }
            } catch (Exception e) {
                Log.e( "Medicine_MainActivity", "解析药物信息出错: " + e.getMessage() );
            }
        }

        if (nearestMedicineName != null) {
            return new String[]{nearestMedicineName, nearestMedicineTime, nearestMedicineDosage};
        }

        return null;
    }

    // 辅助方法：从字符串中提取指定标记之间的值
    private String extractValue(String source, String startTag, String endTag) {
        int startIndex = source.indexOf( startTag );
        if (startIndex == -1) return null;

        startIndex += startTag.length();
        int endIndex = source.indexOf( endTag, startIndex );
        if (endIndex == -1) {
            // 如果找不到结束标记，可能是最后一个属性
            return source.substring( startIndex );
        }

        return source.substring( startIndex, endIndex );
    }


    @Override
    protected void onDestroy() {
        super.onDestroy();
        try {
            if (mBluetoothSocket.isConnected()) {
                //关闭socket
                mBluetoothSocket.close();
                mBlueToothAdapter = null;
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

    //发送数据的方法

    private void sendMessage(String contentStr) {
        if (mBluetoothSocket.isConnected()) {
            try {
                //获取输出流
                mOS = mBluetoothSocket.getOutputStream();
                if (mOS != null) {
                    //写数据（参数为byte数组）
                    mOS.write( ("@" + contentStr + "\r\n").getBytes( "GBK" ) );
                }
            } catch (IOException e) {
                e.printStackTrace();
            }
        } else {
            Toast.makeText( this, "没有设备已连接", Toast.LENGTH_SHORT ).show();
        }
    }

    // 发送当前时间的方法
    private void sendCurrentTime() {
        SimpleDateFormat sdf = new SimpleDateFormat( "HH:mm:ss", Locale.getDefault() );
        String currentTime = sdf.format( new Date() );
        sendMessage( "!," + currentTime );
    }

    // 发送药物信息的方法
    private void sendMedicineInfo() {
        String nextMedicineTime = nextMedicineTimeTextView.getText().toString().replace( "下次吃药时间: ", "" );
        String medicineName = medicineNameTextView.getText().toString().replace( "药名: ", "" );
        String medicineDosage = medicineDosageTextView.getText().toString().replace( "药量: ", "" );

        String message = "*," + nextMedicineTime + "," + medicineName + "," + medicineDosage;
        sendMessage( message );
    }
    private void sendMedicineInfof(String medicineInfo) {
        // 1. 检查输入字符串是否有效
        if (medicineInfo == null || medicineInfo.trim().isEmpty()) {
            Log.w("Medicine_MainActivity", "sendMedicineInfof 收到 null 或空的 medicineInfo，不发送。");
            return; // 没有信息可发送
        }

        // 2. 按 "; " 分割药品条目
        String[] medicines = medicineInfo.split("; ");

        // 3. 确定要处理的药品条目数量（最多 MAX_MEDS_TO_SEND 或 数组实际长度，取较小者）
        int loopLimit = Math.min(medicines.length, MAX_MEDS_TO_SEND);

        Log.d("Medicine_MainActivity", "准备处理最多 " + MAX_MEDS_TO_SEND + " 条药品信息。实际输入条目数: " + medicines.length + "，将处理: " + loopLimit + " 条。");

        int sentCount = 0; // 记录实际成功发送的数量

        // 4. 循环处理每个药品条目
        for (int i = 0; i < loopLimit; i++) {
            // 检查分割后的单个条目是否有效
            if (medicines[i] == null || medicines[i].trim().isEmpty()) {
                Log.w("Medicine_MainActivity", "跳过索引 " + i + " 处的空药品条目。");
                continue; // 处理下一个条目
            }

            try {
                // 5. 提取药品名称、时间和用量
                String name = extractValue(medicines[i], "药名: ", ",");
                String timeStr = extractValue(medicines[i], "吃药时间: ", ",");
                // 假设用量信息后总是有分号";"或其他明确的结束符，以便 extractValue 工作
                // 如果用量是最后一个字段且后面没有结束符，extractValue 需要能处理这种情况
                String dosage = extractValue(medicines[i], "用量: ", ";"); // 或者根据实际格式调整结束标记

                // 6. 检查提取结果是否都有效（不为 null）
                if (name == null || timeStr == null || dosage == null) {
                    Log.w("Medicine_MainActivity", "在索引 " + i + " 处解析药品信息失败 (某些字段为null): " + medicines[i]);
                    continue; // 跳过这条无效信息，处理下一个条目
                }

                // 7. 格式化消息并发送
                String message = "*," + timeStr.trim() + "," + name.trim() + "," + dosage.trim(); // trim() 移除可能的前后空格
                Log.d("Medicine_MainActivity", "准备发送第 " + (i + 1) + " 条有效药品信息: " + message);
                sendMessage(message); // 调用发送蓝牙消息的方法
                sentCount++;

            } catch (Exception e) {
                // 捕获处理单个条目时可能发生的任何意外错误
                Log.e("Medicine_MainActivity", "处理索引 " + i + " 处的药品条目时发生异常: " + medicines[i], e);
                // 选择继续处理下一个条目
                continue;
            }
        }
        Log.d("Medicine_MainActivity", "sendMedicineInfof 完成，共成功发送 " + sentCount + " 条药品信息。");
    }
    /**
     * 与目标设备建立连接
     */
    private void connectDevice() {
        // 获取默认蓝牙适配器
        mBlueToothAdapter = BluetoothAdapter.getDefaultAdapter();
        if (mAddress == null || mAddress.isEmpty()) {
            Toast.makeText( this, "无效的蓝牙地址", Toast.LENGTH_SHORT ).show();
            return;
        }

        // 通过地址拿到该蓝牙设备
        mDevice = mBlueToothAdapter.getRemoteDevice( mAddress );
        if (mDevice == null) {
            Toast.makeText( this, "无法找到设备", Toast.LENGTH_SHORT ).show();
            return;
        }

        try {
            // 建立socket通信
            mBluetoothSocket = mDevice.createRfcommSocketToServiceRecord( mUUID );
            getPermision();
            mBluetoothSocket.connect();
            isBluetoothConnected = true;
            // 连接成功
            Toast.makeText( this, "连接成功", Toast.LENGTH_SHORT ).show();
            // 开启接收数据的线程
            ReceiveDataThread thread = new ReceiveDataThread();
            thread.start();
        } catch (IOException e) {
            e.printStackTrace();
            Toast.makeText( this, "连接出错！" + e.getMessage(), Toast.LENGTH_SHORT ).show();
            Log.e( "cuowu", "连接出错" + e.getMessage(), e );
            finish();
            if (mBluetoothSocket != null) {
                try {
                    mBluetoothSocket.close();
                } catch (IOException ioException) {
                    ioException.printStackTrace();
                }
            }
        }
    }

    /**
     * 动态申请权限
     */
    public void getPermision() {
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.S) {
            requestList.add( Manifest.permission.BLUETOOTH_SCAN );
            requestList.add( Manifest.permission.BLUETOOTH_ADVERTISE );
            requestList.add( Manifest.permission.BLUETOOTH_CONNECT );
            requestList.add( Manifest.permission.ACCESS_FINE_LOCATION );
            requestList.add( Manifest.permission.ACCESS_COARSE_LOCATION );
            requestList.add( Manifest.permission.BLUETOOTH );
        }
        if (requestList.size() != 0) {
            ActivityCompat.requestPermissions( this, requestList.toArray( new String[0] ), 1 );
        }
    }

    /**
     * 负责接收数据的线程
     */
    public class ReceiveDataThread extends Thread {
        private InputStream inputStream;

        public ReceiveDataThread() {
            super();
            try {
                //获取连接socket的输入流
                inputStream = mBluetoothSocket.getInputStream();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }

        @Override
        public void run() {
            super.run();
            int len = 0;
            byte[] buffer = new byte[256];

            while (true) {
                try {
                    inputStream.read( buffer );
                    for (byte b : buffer) {
                    }
                    //设置GBK格式可以获取到中文信息，不会乱码
                    String a = new String( buffer, 0, buffer.length - 3, "GBK" );//为什么-3看文章最后注意部分

                    runOnUiThread( new Runnable() {
                        @Override
                        public void run() {
                            String[] the_spglit = a.split( "," );
                            if (the_spglit.length >= 2) {
                                temperatureHumidityTextView.setText( "药盒温湿度:  " + the_spglit[1] + " ℃, " + the_spglit[2] + " %" );
                            }
                        }
                    } );
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
        }
    }

    // 新增检查吃药时间的方法
    private void checkMedicineTime() {
        // 如果已经显示对话框，直接返回
        if (isDialogShowing) {
            return;
        }

        SimpleDateFormat sdf = new SimpleDateFormat("HH:mm", Locale.getDefault());
        String currentTime = sdf.format(new Date());
        String nextMedicineTime = nextMedicineTimeTextView.getText().toString().replace("下次吃药时间: ", "");

        // 检查是否是当前时间且不是上次已提醒的时间
        if (currentTime.equals(nextMedicineTime) && !currentTime.equals(lastReminderTime)) {
            // 记录这次提醒的时间，防止重复提醒
            lastReminderTime = currentTime;

            String medicineName = medicineNameTextView.getText().toString().replace("药名: ", "");
            String medicineDosage = medicineDosageTextView.getText().toString().replace("药量: ", "");
            String reminderMessage = "提醒,该吃 " + medicineName + " 了，药量: " + medicineDosage;

            // 标记对话框正在显示
            isDialogShowing = true;

            runOnUiThread(() -> {
                AlertDialog dialog = new AlertDialog.Builder(this)
                        .setTitle("吃药提醒")
                        .setMessage(reminderMessage)
                        .setCancelable(false) // 防止点击外部关闭
                        .setPositiveButton("确定", null) // 先设置为null，稍后自定义点击事件
                        .create();

                // 设置按钮点击事件
                dialog.setOnShowListener(dialogInterface -> {
                    Button button = dialog.getButton(AlertDialog.BUTTON_POSITIVE);
                    button.setOnClickListener(view -> {
                        try {
                            // 立即停止提醒音和震动
                            stopAlarmSound();
                            Vibrator vibrator = (Vibrator) getSystemService(Context.VIBRATOR_SERVICE);
                            if (vibrator != null) {
                                vibrator.cancel();
                            }


                            // 强制刷新界面

                            loadMedicinesFromDatabase(); // 从数据库重新加载
                            updateNextMedicineTime();    // 计算最新时间
                            updateNextMedicineTime();
                            sendMedicineInfo();          // 同步硬件
                            sendMessage("#,0");


                            // 记录日志
                            Log.d("Medicine_MainActivity", "用户确认服药: " + medicineName +
                                    ", 更新了下次服药时间和硬件显示");

                            // 关闭对话框
                            dialog.dismiss();
                        } catch (Exception e) {
                            Log.e("Medicine_MainActivity", "处理确认服药时出错: " + e.getMessage());
                        } finally {
                            // 确保标志被重置
                            isDialogShowing = false;
                        }
                    });
                });

                // 对话框关闭时重置标志
                dialog.setOnDismissListener(dialogInterface -> {
                    isDialogShowing = false;
                });

                dialog.show();

                // 播放提醒音和震动
                playNotificationSound();
                Vibrator vibrator = (Vibrator) getSystemService(Context.VIBRATOR_SERVICE);
                if (vibrator != null) {
                    vibrator.vibrate(1000);
                }
                sendMessage("#,1");
            });
        }
    }

    // 添加更新药物库存的方法
    private void updateMedicineStock(String medicineName) {
        try {
            // 在本地列表中查找并更新药物库存
            for (Medicine medicine : medicineList) {
                if (medicine.getName().equals( medicineName )) {
                    int currentStock = medicine.getStock();
                    int dosage = Integer.parseInt( medicine.getDosage() );
                    if (currentStock > 0) {
                        // 设置新的库存值
                        int newStock = currentStock - dosage;


                        // 立即更新数据库
                        new UpdateStockTask( medicine, newStock ).execute();

                        // 记录日志
                        Log.d( "MedicineActivity", "更新库存: " + medicineName +
                                " 从 " + currentStock + " 减少到 " + newStock );

                        // 如果库存低于等于3，显示警告
                        if (newStock <= 3) {
                            showStockAlert( medicine );
                        }
                    }
                    break;
                }
            }
        } catch (Exception e) {
            Log.e( "MedicineActivity", "更新库存失败: " + e.getMessage() );
            Toast.makeText( this, "更新库存失败", Toast.LENGTH_SHORT ).show();
        }
    }

    private void checkMedicineStockAndExpiry() {
        for (Medicine medicine : medicineList) {
            // 检查库存
            if (medicine.getStock() <= 3) {
                showStockAlert(medicine);
            }

            // 检查过期时间
            try {
                SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd", Locale.getDefault());
                Date expiryDate = sdf.parse(medicine.getExpirationDate());
                Date currentDate = new Date();

                // 计算日期差
                long diff = expiryDate.getTime() - currentDate.getTime();
                long daysUntilExpiry = diff / (24 * 60 * 60 * 1000);

                if (daysUntilExpiry <= 7 && daysUntilExpiry > 0) {
                    showExpiryAlert(medicine, daysUntilExpiry);
                }
            } catch (ParseException e) {
                Log.e("Medicine_MainActivity", "解析日期出错: " + e.getMessage());
            }
        }
    }

    // 添加更新数据库库存的异步任务
    private class UpdateStockTask extends AsyncTask<Void, Void, Boolean> {
        private final Medicine medicineToUpdate;
        private final int newstock;
        public UpdateStockTask(Medicine oldMed,int newstock) {
            this.medicineToUpdate = oldMed;
            this.newstock = newstock;
        }

        @Override
        protected Boolean doInBackground(Void... voids) {
            Connection connection = null;
            PreparedStatement stmt = null;
            try {
                Class.forName( "com.mysql.jdbc.Driver" );
                connection = DriverManager.getConnection( DB_URL, DB_USER, DB_PASSWORD );

                String updateQuery = "UPDATE medicines SET stock = ? WHERE medicine_name = ?";
                stmt = connection.prepareStatement( updateQuery );
                stmt.setInt( 1, newstock);
                stmt.setString( 2, medicineToUpdate.getName() );

                int rowsAffected = stmt.executeUpdate();
                Log.d( "UpdateStockTask", "影响的行数: " + rowsAffected );
                return rowsAffected > 0;

            } catch (Exception e) {
                Log.e( "UpdateStockTask", "更新库存失败: " + e.getMessage() );
                return false;
            }
        }

        @Override
        protected void onPostExecute(Boolean success) {
            if (success) {
                // 直接更新本地medicineList中的库存
                for (Medicine medicine : medicineList) {
                    if (medicine.getName().equals(medicineToUpdate.getName())) {
                        medicine.setStock(newstock);
                        break;
                    }
                }
                // 更新界面显示
                runOnUiThread(() -> {
                    updateNextMedicineTime(); // 这会触发sendMedicineInfo
                    Toast.makeText(Medicine_MainActivity.this, "库存已更新", Toast.LENGTH_SHORT).show();
                });
            } else {
                Toast.makeText(Medicine_MainActivity.this, "更新失败", Toast.LENGTH_SHORT).show();
            }
        }
    }

    // 修改显示库存警告的方法
    private void showStockAlert(Medicine medicine) {
        // 在主线程中运行UI操作
        runOnUiThread(() -> {
            new AlertDialog.Builder(this)
                    .setTitle("库存警告")
                    .setMessage(medicine.getName() + " 库存不足，仅剩 " + medicine.getStock() + " 个单位")
                    .setPositiveButton("确定", null)
                    .show();

            // 记录日志
            Log.d("Medicine_MainActivity", "显示库存警告: " + medicine.getName() + ", 剩余: " + medicine.getStock());
        });
    }


    private void showExpiryAlert(Medicine medicine, long daysLeft) {
        // 在主线程中运行UI操作
        runOnUiThread(() -> {
            new AlertDialog.Builder(this)
                    .setTitle("过期提醒")
                    .setMessage(medicine.getName() + " 将在 " + daysLeft + " 天后过期")
                    .setPositiveButton("确定", null)
                    .show();

            // 记录日志
            Log.d("Medicine_MainActivity", "显示过期提醒: " + medicine.getName() + ", 剩余天数: " + daysLeft);
        });
    }

    private void updateNextMedicineTime() {
        // 从数据库中重新加载药品信息
        loadMedicinesFromDatabase();
        // 重新计算最近的服药时间
        String medicineInfo = getMedicineInfoFromList();
        String[] nearestMedicineDetails = findNearestMedicine( medicineInfo );
        if (nearestMedicineDetails != null) {
            nextMedicineTimeTextView.setText( "下次吃药时间: " + nearestMedicineDetails[1] );
            medicineNameTextView.setText( "药名: " + nearestMedicineDetails[0] );
            medicineDosageTextView.setText( "药量: " + nearestMedicineDetails[2] );
        } else {
            nextMedicineTimeTextView.setText( "下次吃药时间: 无" );
            medicineNameTextView.setText( "药名: 无" );
            medicineDosageTextView.setText( "药量: 无" );

        }
        // 同步到硬件设备
        sendMedicineInfo();
    }

    private void loadMedicinesFromDatabase() {
        // 数据库配置
        String DB_URL = "jdbc:mysql://47.113.205.150:3306/test_user?useUnicode=true&characterEncoding=UTF-8&serverTimezone=UTC";
        String DB_USER = "test_user";
        String DB_PASSWORD = "rYEraaXZfmWTGad3";

        // 清空当前药品列表
        medicineList.clear();

        // 加载药品信息
        try {
            Class.forName( "com.mysql.cj.jdbc.Driver" ); // 确保使用正确的驱动类
            Connection connection = DriverManager.getConnection( DB_URL, DB_USER, DB_PASSWORD );

            String query = "SELECT * FROM medicines";
            Statement statement = connection.createStatement();
            ResultSet resultSet = statement.executeQuery( query );

            while (resultSet.next()) {
                String name = resultSet.getString( "medicine_name" );
                String expirationDate = resultSet.getString( "expiry_date" );
                String intakeTimesStr = resultSet.getString( "intake_times" );
                String dosage = resultSet.getString( "dosage" );


                // 将字符串形式的吃药时间转换为List
                List<String> intakeTimes = Arrays.asList( intakeTimesStr.split( "," ) );

                // 创建Medicine对象并添加到列表
                Medicine medicine = new Medicine( name, expirationDate, intakeTimes, dosage );
                medicineList.add( medicine );

                // 检查库存和过期时间
                checkMedicineStockAndExpiry();
            }

            resultSet.close();
            statement.close();
            connection.close();
        } catch (Exception e) {
            e.printStackTrace();
            //Toast.makeText(this, "加载药品信息失败: " + e.getMessage(), Toast.LENGTH_LONG).show();
        }
    }

    private String getMedicineInfoFromList() {
        StringBuilder medicineInfo = new StringBuilder();
        for (Medicine medicine : medicineList) {
            medicineInfo.append( "药名: " ).append( medicine.getName() )
                    .append( ", 过期时间: " ).append( medicine.getExpirationDate() )
                    .append( ", 吃药时间: " ).append( String.join( ", ", medicine.getIntakeTimes() ) )
                    .append( ", 用量: " ).append( medicine.getDosage() ).append( ", " );
        }
        return medicineInfo.toString();
    }

    private void playNotificationSound() {
        // 如果已经在播放，则不重复播放
        if (isPlayingAlarmSound) {
            return;
        }

        isPlayingAlarmSound = true;

        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
            NotificationManager notificationManager = (NotificationManager) getSystemService( Context.NOTIFICATION_SERVICE );
            String channelId = "medicine_reminder_channel";
            if (notificationManager != null) {
                NotificationChannel channel = new NotificationChannel(
                        channelId,
                        "Medicine Reminder Channel",
                        NotificationManager.IMPORTANCE_HIGH
                );
                AudioAttributes audioAttributes = new AudioAttributes.Builder()
                        .setContentType( AudioAttributes.CONTENT_TYPE_SONIFICATION )
                        .setUsage( AudioAttributes.USAGE_ALARM )
                        .build();
                channel.setSound( RingtoneManager.getDefaultUri( RingtoneManager.TYPE_ALARM ), audioAttributes );
                notificationManager.createNotificationChannel( channel );

                NotificationCompat.Builder builder = new NotificationCompat.Builder( this, channelId )
                        .setSmallIcon( android.R.drawable.ic_dialog_alert )
                        .setContentTitle( "吃药提醒" )
                        .setContentText( "该吃药了" )
                        .setPriority( NotificationCompat.PRIORITY_HIGH )
                        .setAutoCancel( true );

                // 明确指定 PendingIntent 的标志
                PendingIntent pendingIntent = PendingIntent.getActivity(
                        this,
                        0,
                        new Intent( this, Medicine_MainActivity.class ),
                        PendingIntent.FLAG_UPDATE_CURRENT | PendingIntent.FLAG_IMMUTABLE
                );
                builder.setContentIntent( pendingIntent );

                Notification notification = builder.build();
                notificationManager.notify( 1, notification );

                // 为通知声音手动播放铃声5秒（修改为5秒）
                playAlarmSound();
            }
        } else {
            Uri notification = RingtoneManager.getDefaultUri( RingtoneManager.TYPE_ALARM );
            // 释放旧的MediaPlayer（如果存在）
            if (currentMediaPlayer != null) {
                currentMediaPlayer.release();
            }
            currentMediaPlayer = MediaPlayer.create( this, notification );
            if (currentMediaPlayer != null) {
                currentMediaPlayer.setLooping( true ); // 设置循环播放
                currentMediaPlayer.start();

                // 设置5秒后自动停止（修改为5秒）
                alarmTimer = new CountDownTimer( 5000, 5000 ) {
                    @Override
                    public void onTick(long millisUntilFinished) {
                        // 不需要做任何事
                    }

                    @Override
                    public void onFinish() {
                        stopAlarmSound();
                    }
                }.start();
            }
        }
    }

    private void playAlarmSound() {
        try {
            // 停止之前可能正在播放的铃声
            stopAlarmSound();

            // 创建新的MediaPlayer并开始播放
            Uri alarmSound = RingtoneManager.getDefaultUri( RingtoneManager.TYPE_ALARM );
            currentMediaPlayer = MediaPlayer.create( this, alarmSound );
            if (currentMediaPlayer != null) {
                currentMediaPlayer.setLooping( true ); // 设置循环播放
                currentMediaPlayer.start();

                // 设置5秒后自动停止
                alarmStopHandler.postDelayed( new Runnable() {
                    @Override
                    public void run() {
                        stopAlarmSound();
                    }
                }, 5000 ); // 10秒
            }
        } catch (Exception e) {
            Log.e( "MedicineActivity", "播放提醒音失败", e );
        }
    }

    private void stopAlarmSound() {
        try {
            // 停止当前的MediaPlayer
            if (currentMediaPlayer != null) {
                if (currentMediaPlayer.isPlaying()) {
                    currentMediaPlayer.stop();
                }
                currentMediaPlayer.release();
                currentMediaPlayer = null;
            }

            // 重置标志位
            isPlayingAlarmSound = false;

            // 取消定时器
            if (alarmTimer != null) {
                alarmTimer.cancel();
                alarmTimer = null;
            }

            // 清除所有可能的延迟停止任务
            alarmStopHandler.removeCallbacksAndMessages(null);

            Log.d("MedicineActivity", "提醒音已停止");
        } catch (Exception e) {
            Log.e("MedicineActivity", "停止提醒音失败: " + e.getMessage());
        }
    }


}